home *** CD-ROM | disk | FTP | other *** search
/ Graphics Plus / Graphics Plus.iso / libs / tsipp / tsipp.lha / tsipp3.0a / src / tSippObj.c < prev    next >
Encoding:
C/C++ Source or Header  |  1992-11-02  |  29.0 KB  |  876 lines

  1. /*
  2.  *=============================================================================
  3.  *                                  tSippObj.c
  4.  *-----------------------------------------------------------------------------
  5.  * Tcl commands to manage SIPP objects.
  6.  *-----------------------------------------------------------------------------
  7.  * Copyright 1992 Mark Diekhans
  8.  * Permission to use, copy, modify, and distribute this software and its
  9.  * documentation for any purpose and without fee is hereby granted, provided
  10.  * that the above copyright notice appear in all copies.  Mark Diekhans makes
  11.  * no representations about the suitability of this software for any purpose.
  12.  * It is provided "as is" without express or implied warranty.
  13.  *-----------------------------------------------------------------------------
  14.  * $Id: tSippObj.c,v 2.0 1992/11/02 03:56:26 markd Rel $
  15.  *=============================================================================
  16.  */
  17.  
  18. #include "tSippInt.h"
  19.  
  20. /*
  21.  * Internal function prototypes.
  22.  */
  23. static Object *
  24. ObjectHandleCmdSetup _ANSI_ARGS_((tSippGlob_pt   tSippGlobPtr,
  25.                                   int            argc,
  26.                                   char         **argv));
  27.  
  28. static Object *
  29. ObjectAxisRotSetup _ANSI_ARGS_((tSippGlob_pt   tSippGlobPtr,
  30.                                 int            argc,
  31.                                 char         **argv,
  32.                                 double        *anglePtr));
  33.  
  34. /*=============================================================================
  35.  * TSippBindObjectToHandle --
  36.  *   Assigns a handle to the specified object.
  37.  * Parameters:
  38.  *   o tSippGlobPtr (I) - Pointer to the Tcl SIPP globals. The handle is
  39.  *     returned in interp->result.
  40.  *   o objectPtr (I) - A pointer to the object.
  41.  *-----------------------------------------------------------------------------
  42.  */
  43. void
  44. TSippBindObjectToHandle (tSippGlobPtr, objectPtr)
  45.     tSippGlob_pt    tSippGlobPtr;
  46.     Object         *objectPtr;
  47. {
  48.     Object  **objectEntryPtr;
  49.  
  50.     objectEntryPtr = (Object **)
  51.         Tcl_HandleAlloc (tSippGlobPtr->objectTblPtr, 
  52.                          tSippGlobPtr->interp->result);
  53.     *objectEntryPtr = objectPtr;
  54.  
  55. } /* TSippBindObjectToHandle */
  56.  
  57. /*=============================================================================
  58.  * TSippObjectHandleToPtr --
  59.  *   Utility procedure to convert an object handle to an object pointer.
  60.  * For use of by functions outside of this module. Checks for magic handle
  61.  * "WORLD".
  62.  *
  63.  * Parameters:
  64.  *   o tSippGlobPtr (I) - A pointer to the Tcl SIPP global structure.
  65.  *   o handle (I) - A object handle.
  66.  * Returns:
  67.  *   A pointer to the object, or NULL if an error occured.
  68.  *-----------------------------------------------------------------------------
  69.  */
  70. Object *
  71. TSippObjectHandleToPtr (tSippGlobPtr, handle)
  72.     tSippGlob_pt    tSippGlobPtr;
  73.     char           *handle;
  74. {
  75.     Object **objectEntryPtr;
  76.  
  77.     if ((handle [0] == 'W') && (STREQU (handle, "WORLD")))
  78.         return sipp_world;
  79.  
  80.     objectEntryPtr = (Object **)
  81.         Tcl_HandleXlate (tSippGlobPtr->interp, 
  82.                          tSippGlobPtr->objectTblPtr, handle);
  83.     if (objectEntryPtr == NULL)
  84.         return NULL;
  85.     return *objectEntryPtr;
  86.  
  87. } /* TSippObjectHandleToPtr */
  88.  
  89. /*=============================================================================
  90.  * ObjectHandleCmdSetup --
  91.  *    Utility procedure for the commands that take a single argument of an
  92.  * object handle.  Validates argv and retrieves the handle table entry.
  93.  *
  94.  * Parameters:
  95.  *   o tSippGlobPtr (I) - A pointer to the Tcl SIPP global structure.
  96.  *   o argc, argv (I) - Command argument vector.
  97.  * Returns:
  98.  *   A pointer to the object associated with the handle or NULL and an error
  99.  *   in tSippGlobPtr->interp->result if an error occurs.
  100.  *-----------------------------------------------------------------------------
  101.  */
  102. static Object *
  103. ObjectHandleCmdSetup (tSippGlobPtr, argc, argv)
  104.     tSippGlob_pt   tSippGlobPtr;
  105.     int            argc;
  106.     char         **argv;
  107. {
  108.  
  109.     if (argc != 2) {
  110.         Tcl_AppendResult (tSippGlobPtr->interp, "wrong # args: ", argv [0],
  111.                           " objecthandle", (char *) NULL);
  112.         return NULL;
  113.     }
  114.     return TSippObjectHandleToPtr (tSippGlobPtr, argv [1]);
  115.  
  116. } /* ObjectHandleCmdSetup */
  117.  
  118. /*=============================================================================
  119.  * SippObjectCreate --
  120.  *   Implements the command:
  121.  *     SippObjectCreate
  122.  * Note:
  123.  *   This procedure has standard Tcl command calling sematics.  ClientData
  124.  * contains a pointer to the Tcl SIPP global structure.
  125.  *-----------------------------------------------------------------------------
  126.  */
  127. static int
  128. SippObjectCreate (clientData, interp, argc, argv)
  129.     char       *clientData;
  130.     Tcl_Interp *interp;
  131.     int         argc;
  132.     char      **argv;
  133. {
  134.     if (argc != 1) {
  135.         Tcl_AppendResult (interp, "wrong # args: ", argv[0], (char *) NULL);
  136.         return TCL_ERROR;
  137.     }                     
  138.     TSippBindObjectToHandle ((tSippGlob_pt) clientData, object_create ());
  139.     return TCL_OK;
  140.  
  141. } /* SippObjectCreate */
  142.  
  143. /*=============================================================================
  144.  * SippObjectDelete --
  145.  *   Implements the command:
  146.  *     SippObjectDelete objectlist
  147.  * Note:
  148.  *   This procedure has standard Tcl command calling sematics.  ClientData
  149.  * contains a pointer to the Tcl SIPP global structure.
  150.  *-----------------------------------------------------------------------------
  151.  */
  152. static int
  153. SippObjectDelete (clientData, interp, argc, argv)
  154.     char       *clientData;
  155.     Tcl_Interp *interp;
  156.     int         argc;
  157.     char      **argv;
  158. {
  159.     tSippGlob_pt    tSippGlobPtr = (tSippGlob_pt) clientData;
  160.     int             idx;
  161.     handleList_t    objectList;
  162.     handleList_t    objectEntryList;
  163.  
  164.     if (argc != 2) {
  165.         Tcl_AppendResult (interp, "wrong # args: ", argv [0],
  166.                           " objectlist", (char *) NULL);
  167.         return TCL_ERROR;
  168.     }                     
  169.     if (!TSippHandleListConvert (tSippGlobPtr, tSippGlobPtr->objectTblPtr,
  170.                                  argv [1], &objectList, &objectEntryList))
  171.         return TCL_ERROR;
  172.  
  173.     for (idx = 0; idx < objectList.len; idx++) {
  174.         object_delete ((Object *) objectList.ptr [idx]);
  175.         Tcl_HandleFree (tSippGlobPtr->objectTblPtr, objectEntryList.ptr [idx]);
  176.     }
  177.  
  178.     TSippHandleListFree (&objectList);
  179.     TSippHandleListFree (&objectEntryList);
  180.     return TCL_OK;
  181.  
  182. } /* SippObjectDelete */
  183.  
  184. /*=============================================================================
  185.  * SippObjectInstance --
  186.  *   Implements the command:
  187.  *     SippObjectInstance objecthandle
  188.  * Note:
  189.  *   This procedure has standard Tcl command calling sematics.  ClientData
  190.  * contains a pointer to the Tcl SIPP global structure.
  191.  *-----------------------------------------------------------------------------
  192.  */
  193. static int
  194. SippObjectInstance (clientData, interp, argc, argv)
  195.     char       *clientData;
  196.     Tcl_Interp *interp;
  197.     int         argc;
  198.     char      **argv;
  199. {
  200.     Object  *objectPtr;
  201.  
  202.     objectPtr = ObjectHandleCmdSetup ((tSippGlob_pt) clientData, argc, argv);
  203.     if (objectPtr == NULL)
  204.         return TCL_ERROR;    
  205.  
  206.     TSippBindObjectToHandle ((tSippGlob_pt) clientData,
  207.                              object_instance (objectPtr));
  208.     return TCL_OK;
  209.  
  210. } /* SippObjectInstance */
  211.  
  212. /*=============================================================================
  213.  * SippObjectDup --
  214.  *   Implements the command:
  215.  *     SippObjectDup objecthandle
  216.  * Note:
  217.  *   This procedure has standard Tcl command calling sematics.  ClientData
  218.  * contains a pointer to the Tcl SIPP global structure.
  219.  *-----------------------------------------------------------------------------
  220.  */
  221. static int
  222. SippObjectDup (clientData, interp, argc, argv)
  223.     char       *clientData;
  224.     Tcl_Interp *interp;
  225.     int         argc;
  226.     char      **argv;
  227. {
  228.     Object  *objectPtr;
  229.  
  230.     objectPtr = ObjectHandleCmdSetup ((tSippGlob_pt) clientData, argc, argv);
  231.     if (objectPtr == NULL)
  232.         return TCL_ERROR;    
  233.  
  234.     TSippBindObjectToHandle ((tSippGlob_pt) clientData, 
  235.                               object_dup (objectPtr));
  236.     return TCL_OK;
  237.  
  238. } /* SippObjectDup */
  239.  
  240. /*=============================================================================
  241.  * SippObjectDeepDup --
  242.  *   Implements the command:
  243.  *     SippObjectDeepDup objecthandle
  244.  * Note:
  245.  *   This procedure has standard Tcl command calling sematics.  ClientData
  246.  * contains a pointer to the Tcl SIPP global structure.
  247.  *-----------------------------------------------------------------------------
  248.  */
  249. static int
  250. SippObjectDeepDup (clientData, interp, argc, argv)
  251.     char       *clientData;
  252.     Tcl_Interp *interp;
  253.     int         argc;
  254.     char      **argv;
  255. {
  256.     Object  *objectPtr;
  257.  
  258.     objectPtr = ObjectHandleCmdSetup ((tSippGlob_pt) clientData, argc, argv);
  259.     if (objectPtr == NULL)
  260.         return TCL_ERROR;    
  261.  
  262.     TSippBindObjectToHandle ((tSippGlob_pt) clientData,
  263.                               object_deep_dup (objectPtr));
  264.     return TCL_OK;
  265.  
  266. } /* SippObjectDeepDup */
  267.  
  268. /*=============================================================================
  269.  * SippObjectGetTransf --
  270.  *   Implements the command:
  271.  *     SippObjectGetTransf objecthandle
  272.  * Note:
  273.  *   This procedure has standard Tcl command calling sematics.  ClientData
  274.  * contains a pointer to the Tcl SIPP global structure.
  275.  *-----------------------------------------------------------------------------
  276.  */
  277. static int
  278. SippObjectGetTransf (clientData, interp, argc, argv)
  279.     char       *clientData;
  280.     Tcl_Interp *interp;
  281.     int         argc;
  282.     char      **argv;
  283. {
  284.     tSippGlob_pt    tSippGlobPtr = (tSippGlob_pt) clientData;
  285.     Object         *objectPtr;
  286.     Transf_mat      matrix;
  287.  
  288.     objectPtr = ObjectHandleCmdSetup ((tSippGlob_pt) clientData, argc, argv);
  289.     if (objectPtr == NULL)
  290.         return TCL_ERROR;    
  291.  
  292.     object_get_transf (objectPtr, &matrix);
  293.     Tcl_SetResult (interp, TSippFormatMatrix (&matrix), TCL_DYNAMIC);
  294.  
  295.     return TCL_OK;
  296.  
  297. } /* SippObjectGetTransf */
  298.  
  299. /*=============================================================================
  300.  * SippObjectSetTransf --
  301.  *   Implements the command:
  302.  *     SippObjectSetTransf objectlist matrix
  303.  * Note:
  304.  *   This procedure has standard Tcl command calling sematics.  ClientData
  305.  * contains a pointer to the Tcl SIPP global structure.
  306.  *-----------------------------------------------------------------------------
  307.  */
  308. static int
  309. SippObjectSetTransf (clientData, interp, argc, argv)
  310.     char       *clientData;
  311.     Tcl_Interp *interp;
  312.     int         argc;
  313.     char      **argv;
  314. {
  315.     tSippGlob_pt    tSippGlobPtr = (tSippGlob_pt) clientData;
  316.     Transf_mat      matrix;
  317.     Object         *objectPtr;
  318.  
  319.     if (argc != 3) {
  320.         Tcl_AppendResult (tSippGlobPtr->interp, "wrong # args: ", argv [0],
  321.                           " objectlist matrix", (char *) NULL);
  322.         return TCL_ERROR;
  323.     }
  324.     objectPtr = TSippObjectHandleToPtr ((tSippGlob_pt) clientData, 
  325.                                          argv [1]);
  326.     if (objectPtr == NULL)
  327.         return TCL_ERROR;
  328.     if (!TSippConvertMatrix (tSippGlobPtr, argv [2], &matrix))
  329.         return TCL_ERROR;
  330.  
  331.     object_set_transf (objectPtr, &matrix);
  332.  
  333.     return TCL_OK;
  334.  
  335. } /* SippObjectSetTransf */
  336.  
  337. /*=============================================================================
  338.  * SippObjectClearTransf --
  339.  *   Implements the command:
  340.  *     SippObjectClearTransf object
  341.  * Note:
  342.  *   This procedure has standard Tcl command calling sematics.  ClientData
  343.  * contains a pointer to the Tcl SIPP global structure.
  344.  *-----------------------------------------------------------------------------
  345.  */
  346. static int
  347. SippObjectClearTransf (clientData, interp, argc, argv)
  348.     char       *clientData;
  349.     Tcl_Interp *interp;
  350.     int         argc;
  351.     char      **argv;
  352. {
  353.     tSippGlob_pt    tSippGlobPtr = (tSippGlob_pt) clientData;
  354.     Object        *objectPtr;
  355.  
  356.     if (argc != 2) {
  357.         Tcl_AppendResult (interp, "wrong # args: ", argv [0],
  358.                           " objectlist", (char *) NULL);
  359.         return TCL_ERROR;
  360.     }                     
  361.     objectPtr = TSippObjectHandleToPtr ((tSippGlob_pt) clientData, 
  362.                                          argv [1]);
  363.     if (objectPtr == NULL)
  364.         return TCL_ERROR;
  365.     object_clear_transf (objectPtr);
  366.  
  367.     return TCL_OK;
  368.  
  369. } /* SippObjectClearTransf */
  370.  
  371. /*=============================================================================
  372.  * SippObjectTransform --
  373.  *   Implements the command:
  374.  *     SippObjectTransform objectlist matrix
  375.  * Note:
  376.  *   This procedure has standard Tcl command calling sematics.  ClientData
  377.  * contains a pointer to the Tcl SIPP global structure.
  378.  *-----------------------------------------------------------------------------
  379.  */
  380. static int
  381. SippObjectTransform (clientData, interp, argc, argv)
  382.     char       *clientData;
  383.     Tcl_Interp *interp;
  384.     int         argc;
  385.     char      **argv;
  386. {
  387.     tSippGlob_pt    tSippGlobPtr = (tSippGlob_pt) clientData;
  388.     Transf_mat      matrix;
  389.     Object        *objectPtr;
  390.     
  391.     if (argc != 3) {
  392.         Tcl_AppendResult (tSippGlobPtr->interp, "wrong # args: ", argv [0],
  393.                           " objectlist matrix", (char *) NULL);
  394.         return TCL_ERROR;
  395.     }
  396.     objectPtr = TSippObjectHandleToPtr ((tSippGlob_pt) clientData, 
  397.                                          argv [1]);
  398.     if (objectPtr == NULL)
  399.         return TCL_ERROR;
  400.     if (!TSippConvertMatrix (tSippGlobPtr, argv [2], &matrix))
  401.         return TCL_ERROR;
  402.  
  403.     object_set_transf (objectPtr, &matrix);
  404.  
  405.     return TCL_OK;
  406.  
  407. } /* SippObjectTransform */
  408.  
  409. /*=============================================================================
  410.  * SippObjectAddSurface --
  411.  *   Implements the command:
  412.  *     SippObjectAddSurface objecthandle surfacelist
  413.  * Note:
  414.  *   This procedure has standard Tcl command calling sematics.  ClientData
  415.  * contains a pointer to the Tcl SIPP global structure.
  416.  *-----------------------------------------------------------------------------
  417.  */
  418. static int
  419. SippObjectAddSurface (clientData, interp, argc, argv)
  420.     char       *clientData;
  421.     Tcl_Interp *interp;
  422.     int         argc;
  423.     char      **argv;
  424. {
  425.     tSippGlob_pt   tSippGlobPtr = (tSippGlob_pt) clientData;
  426.     Object        *objectPtr;
  427.     int            idx;
  428.     handleList_t   surfaceList;
  429.     
  430.     if (argc != 3) {
  431.         Tcl_AppendResult (interp, "wrong # args: ", argv [0],
  432.                           " objecthandle surfacelist", (char *) NULL);
  433.         return TCL_ERROR;
  434.     }                     
  435.     objectPtr = TSippObjectHandleToPtr ((tSippGlob_pt) clientData, 
  436.                                          argv [1]);
  437.     if (objectPtr == NULL)
  438.         return TCL_ERROR;
  439.     if (!TSippHandleListConvert (tSippGlobPtr, tSippGlobPtr->surfaceTblPtr,
  440.                                  argv [2], &surfaceList, NULL))
  441.         return TCL_ERROR;
  442.  
  443.     for (idx = 0; idx < surfaceList.len; idx++)
  444.         object_add_surface (objectPtr, (Surface *) (surfaceList.ptr [idx]));
  445.  
  446.     TSippHandleListFree (&surfaceList);
  447.     return TCL_OK;
  448.  
  449. } /* SippObjectAddSurface */
  450.  
  451. /*=============================================================================
  452.  * SippObjectSubSurface --
  453.  *   Implements the command:
  454.  *     SippObjectSubSurface objecthandle surfacelist
  455.  * Note:
  456.  *   This procedure has standard Tcl command calling sematics.  ClientData
  457.  * contains a pointer to the Tcl SIPP global structure.
  458.  *-----------------------------------------------------------------------------
  459.  */
  460. static int
  461. SippObjectSubSurface (clientData, interp, argc, argv)
  462.     char       *clientData;
  463.     Tcl_Interp *interp;
  464.     int         argc;
  465.     char      **argv;
  466. {
  467.     tSippGlob_pt   tSippGlobPtr = (tSippGlob_pt) clientData;
  468.     Object        *objectPtr;
  469.     int            idx;
  470.     handleList_t   surfaceList;
  471.     
  472.     if (argc != 3) {
  473.         Tcl_AppendResult (interp, "wrong # args: ", argv [0],
  474.                           " objecthandle surfacelist", (char *) NULL);
  475.         return TCL_ERROR;
  476.     }                     
  477.     objectPtr = TSippObjectHandleToPtr ((tSippGlob_pt) clientData, 
  478.                                          argv [1]);
  479.     if (objectPtr == NULL)
  480.         return TCL_ERROR;
  481.     if (!TSippHandleListConvert (tSippGlobPtr, tSippGlobPtr->surfaceTblPtr,
  482.                                  argv [2], &surfaceList, NULL))
  483.         return TCL_ERROR;
  484.  
  485.     for (idx = 0; idx < surfaceList.len; idx++)
  486.         object_sub_surface (objectPtr, (Surface *) (surfaceList.ptr [idx]));
  487.  
  488.     TSippHandleListFree (&surfaceList);
  489.     return TCL_OK;
  490.  
  491. } /* SippObjectSubSurface */
  492.  
  493. /*=============================================================================
  494.  * SippObjectAddSubobj --
  495.  *   Implements the command:
  496.  *     SippObjectAddSubobj objecthandle subobjlist
  497.  * Note:
  498.  *   This procedure has standard Tcl command calling sematics.  ClientData
  499.  * contains a pointer to the Tcl SIPP global structure.
  500.  *-----------------------------------------------------------------------------
  501.  */
  502. static int
  503. SippObjectAddSubobj (clientData, interp, argc, argv)
  504.     char       *clientData;
  505.     Tcl_Interp *interp;
  506.     int         argc;
  507.     char      **argv;
  508. {
  509.     tSippGlob_pt   tSippGlobPtr = (tSippGlob_pt) clientData;
  510.     Object        *objectPtr;
  511.     int            idx;
  512.     handleList_t   subObjList;;
  513.  
  514.     if (argc != 3) {
  515.         Tcl_AppendResult (interp, "wrong # args: ", argv [0], 
  516.                           " objecthandle subobjlist", (char *) NULL);
  517.         return TCL_ERROR;
  518.     }                     
  519.     objectPtr = TSippObjectHandleToPtr ((tSippGlob_pt) clientData, argv [1]);
  520.     if (objectPtr == NULL)
  521.         return TCL_ERROR;
  522.  
  523.     if (!TSippHandleListConvert (tSippGlobPtr, tSippGlobPtr->objectTblPtr,
  524.                                  argv [2], &subObjList, NULL))
  525.         return TCL_ERROR;
  526.     for (idx = 0; idx < subObjList.len; idx++)
  527.         object_add_subobj (objectPtr, (Object *) (subObjList.ptr [idx]));
  528.  
  529.     TSippHandleListFree (&subObjList);
  530.  
  531.     return TCL_OK;
  532.  
  533. } /* SippObjectAddSubobj */
  534.  
  535. /*=============================================================================
  536.  * SippObjectSubSubobj --
  537.  *   Implements the command:
  538.  *     SippObjectSubSubobj objecthandle subobjlist
  539.  * Note:
  540.  *   This procedure has standard Tcl command calling sematics.  ClientData
  541.  * contains a pointer to the Tcl SIPP global structure.
  542.  *-----------------------------------------------------------------------------
  543.  */
  544. static int
  545. SippObjectSubSubobj (clientData, interp, argc, argv)
  546.     char       *clientData;
  547.     Tcl_Interp *interp;
  548.     int         argc;
  549.     char      **argv;
  550. {
  551.     tSippGlob_pt   tSippGlobPtr = (tSippGlob_pt) clientData;
  552.     Object        *objectPtr;
  553.     int            idx;
  554.     handleList_t   subObjList;;
  555.  
  556.     if (argc != 3) {
  557.         Tcl_AppendResult (interp, "wrong # args: ", argv [0], 
  558.                           " objecthandle subobjlist", (char *) NULL);
  559.         return TCL_ERROR;
  560.     }                     
  561.     objectPtr = TSippObjectHandleToPtr ((tSippGlob_pt) clientData, argv [1]);
  562.     if (objectPtr == NULL)
  563.         return TCL_ERROR;
  564.  
  565.     if (!TSippHandleListConvert (tSippGlobPtr, tSippGlobPtr->objectTblPtr,
  566.                                  argv [2], &subObjList, NULL))
  567.         return TCL_ERROR;
  568.     for (idx = 0; idx < subObjList.len; idx++)
  569.         object_sub_subobj (objectPtr, (Object *) (subObjList.ptr [idx]));
  570.  
  571.     TSippHandleListFree (&subObjList);
  572.  
  573.     return TCL_OK;
  574.  
  575. } /* SippObjectSubSubobj */
  576.  
  577. /*=============================================================================
  578.  * ObjectAxisRotSetup --
  579.  *   Process parameters for the commands to rotate an object around an axis.
  580.  * These commands have the arguments: objecthandle angle
  581.  * Parameters:
  582.  *   o tSippGlobPtr (I) - Pointer to the Tcl SIPP globals.
  583.  *   o argc, argv (I) - The arguments to the command.
  584.  *   o anglePtr (O) - The angle to rotate the object is returned here.
  585.  * Returns:
  586.  *   A pointer to the object or NULL if an error occured.
  587.  *-----------------------------------------------------------------------------
  588.  */
  589. static Object *
  590. ObjectAxisRotSetup (tSippGlobPtr, argc, argv, anglePtr)
  591.     tSippGlob_pt   tSippGlobPtr;
  592.     int            argc;
  593.     char         **argv;
  594.     double        *anglePtr;
  595. {
  596.     Object        *objectPtr;
  597.  
  598.     if (argc != 3) {
  599.         Tcl_AppendResult (tSippGlobPtr->interp, "wrong # args: ", argv [0],
  600.                           " object angle", (char *) NULL);
  601.         return NULL;
  602.     }
  603.     objectPtr = TSippObjectHandleToPtr (tSippGlobPtr, argv [1]);
  604.     if (objectPtr == NULL)
  605.         return NULL;
  606.     if (!TSippConvertAngleRad (tSippGlobPtr, argv [2], anglePtr))
  607.         return NULL;
  608.  
  609.    return objectPtr;
  610.  
  611. } /*  ObjectAxisRotSetup */
  612.  
  613. /*=============================================================================
  614.  * SippObjectRotateX --
  615.  *   Implements the command:
  616.  *     SippObjectRotateX object angle
  617.  * Note:
  618.  *   This procedure has standard Tcl command calling sematics.  ClientData
  619.  * contains a pointer to the Tcl SIPP global structure.
  620.  *-----------------------------------------------------------------------------
  621.  */
  622. static int
  623. SippObjectRotateX (clientData, interp, argc, argv)
  624.     char       *clientData;
  625.     Tcl_Interp *interp;
  626.     int         argc;
  627.     char      **argv;
  628. {
  629.     tSippGlob_pt   tSippGlobPtr = (tSippGlob_pt) clientData;
  630.     Object        *objectPtr;
  631.     double         angle;
  632.  
  633.     objectPtr = ObjectAxisRotSetup ((tSippGlob_pt) clientData, argc, argv, 
  634.                                     &angle);
  635.     if (objectPtr == NULL)
  636.         return TCL_ERROR;
  637.  
  638.     object_rot_x (objectPtr, angle);
  639.     return TCL_OK;
  640.  
  641. } /* SippObjectRotateX */
  642.  
  643. /*=============================================================================
  644.  * SippObjectRotateY --
  645.  *   Implements the command:
  646.  *     SippObjectRotateY object angle
  647.  * Note:
  648.  *   This procedure has standard Tcl command calling sematics.  ClientData
  649.  * contains a pointer to the Tcl SIPP global structure.
  650.  *-----------------------------------------------------------------------------
  651.  */
  652. static int
  653. SippObjectRotateY (clientData, interp, argc, argv)
  654.     char       *clientData;
  655.     Tcl_Interp *interp;
  656.     int         argc;
  657.     char      **argv;
  658. {
  659.     tSippGlob_pt   tSippGlobPtr = (tSippGlob_pt) clientData;
  660.     Object        *objectPtr;
  661.     double         angle;
  662.  
  663.     objectPtr = ObjectAxisRotSetup ((tSippGlob_pt) clientData, argc, argv, 
  664.                                     &angle);
  665.     if (objectPtr == NULL)
  666.         return TCL_ERROR;
  667.  
  668.     object_rot_y (objectPtr, angle);
  669.     return TCL_OK;
  670.  
  671. } /* SippObjectRotateY */
  672.  
  673. /*=============================================================================
  674.  * SippObjectRotateZ --
  675.  *   Implements the command:
  676.  *     SippObjectRotateZ object angle
  677.  * Note:
  678.  *   This procedure has standard Tcl command calling sematics.  ClientData
  679.  * contains a pointer to the Tcl SIPP global structure.
  680.  *-----------------------------------------------------------------------------
  681.  */
  682. static int
  683. SippObjectRotateZ (clientData, interp, argc, argv)
  684.     char       *clientData;
  685.     Tcl_Interp *interp;
  686.     int         argc;
  687.     char      **argv;
  688. {
  689.     tSippGlob_pt   tSippGlobPtr = (tSippGlob_pt) clientData;
  690.     Object        *objectPtr;
  691.     double         angle;
  692.  
  693.     objectPtr = ObjectAxisRotSetup ((tSippGlob_pt) clientData, argc, argv, 
  694.                                     &angle);
  695.     if (objectPtr == NULL)
  696.         return TCL_ERROR;
  697.  
  698.     object_rot_z (objectPtr, angle);
  699.     return TCL_OK;
  700.  
  701. } /* SippObjectRotateZ */
  702.  
  703. /*=============================================================================
  704.  * SippObjectRotate --
  705.  *   Implements the command:
  706.  *     SippObjectRotate objecthandle point vector angle
  707.  *
  708.  * Note:
  709.  *   This procedure has standard Tcl command calling sematics.  ClientData
  710.  * contains a pointer to the Tcl SIPP global structure.
  711.  *-----------------------------------------------------------------------------
  712.  */
  713. static int
  714. SippObjectRotate (clientData, interp, argc, argv)
  715.     char       *clientData;
  716.     Tcl_Interp *interp;
  717.     int         argc;
  718.     char      **argv;
  719. {
  720.     tSippGlob_pt   tSippGlobPtr = (tSippGlob_pt) clientData;
  721.     Object        *objectPtr;
  722.     Vector         point, vector;
  723.     double         angle;
  724.  
  725.     if (argc != 5) {
  726.         Tcl_AppendResult (interp, "wrong # args: ", argv [0], 
  727.                           " objecthandle point vector angle", (char *) NULL);
  728.         return TCL_ERROR;
  729.     }                     
  730.     objectPtr =  TSippObjectHandleToPtr (tSippGlobPtr, argv [1]);
  731.     if (objectPtr == NULL)
  732.         return TCL_ERROR;
  733.     if (!TSippConvertVertex (tSippGlobPtr, argv [2], &point))
  734.         return TCL_ERROR;
  735.     if (!TSippConvertVertex (tSippGlobPtr, argv [3], &vector))
  736.         return TCL_ERROR;
  737.     if (!TSippConvertAngleRad (tSippGlobPtr, argv [4], &angle))
  738.         return TCL_ERROR;
  739.  
  740.     object_rot (objectPtr, &point, &vector, angle);
  741.  
  742.     return TCL_OK;
  743.  
  744. } /* SippObjectRotate */
  745.  
  746. /*=============================================================================
  747.  * SippObjectScale --
  748.  *   Implements the command:
  749.  *     SippObjectScale objecthandle factor|{xfactor yfactor zfactor}
  750.  *
  751.  * Note:
  752.  *   This procedure has standard Tcl command calling sematics.  ClientData
  753.  * contains a pointer to the Tcl SIPP global structure.
  754.  *-----------------------------------------------------------------------------
  755.  */
  756. static int
  757. SippObjectScale (clientData, interp, argc, argv)
  758.     char       *clientData;
  759.     Tcl_Interp *interp;
  760.     int         argc;
  761.     char      **argv;
  762. {
  763.     tSippGlob_pt   tSippGlobPtr = (tSippGlob_pt) clientData;
  764.     Object        *objectPtr;
  765.     Vector         scale;
  766.  
  767.     if (argc != 3) {
  768.         Tcl_AppendResult (interp, "wrong # args: ", argv [0], 
  769.                           " objecthandle factor|{xfactor yfactor zfactor}",
  770.                           (char *) NULL);
  771.         return TCL_ERROR;
  772.     }                     
  773.     objectPtr =  TSippObjectHandleToPtr (tSippGlobPtr, argv [1]);
  774.     if (objectPtr == NULL)
  775.         return TCL_ERROR;
  776.     /*
  777.      * Scale can be a list or a single factor.  If it contains any white space
  778.      * assume its a list.
  779.      */
  780.     if (strpbrk (argv [2], " \f\t\n\r\v") == NULL) {
  781.         if (Tcl_GetDouble (interp, argv [2], &scale.x) != TCL_OK)
  782.             return TCL_ERROR;
  783.         scale.y = scale.z = scale.x;
  784.     } else {
  785.         if (!TSippConvertVertex (tSippGlobPtr, argv [2], &scale))
  786.             return TCL_ERROR;
  787.     } 
  788.  
  789.     object_scale (objectPtr, scale.x, scale.y, scale.z);
  790.  
  791.     return TCL_OK;
  792.  
  793. } /* SippObjectScale */
  794.  
  795. /*=============================================================================
  796.  * SippObjectMove --
  797.  *   Implements the command:
  798.  *     SippObjectMove objecthandle {xdist ydist zdist}
  799.  *
  800.  * Note:
  801.  *   This procedure has standard Tcl command calling sematics.  ClientData
  802.  * contains a pointer to the Tcl SIPP global structure.
  803.  *-----------------------------------------------------------------------------
  804.  */
  805. static int
  806. SippObjectMove (clientData, interp, argc, argv)
  807.     char       *clientData;
  808.     Tcl_Interp *interp;
  809.     int         argc;
  810.     char      **argv;
  811. {
  812.     tSippGlob_pt   tSippGlobPtr = (tSippGlob_pt) clientData;
  813.     Object        *objectPtr;
  814.     Vector         translation;
  815.  
  816.     if (argc != 3) {
  817.         Tcl_AppendResult (interp, "wrong # args: ", argv [0], 
  818.                           " objecthandle {xdist ydist zdist}",
  819.                           (char *) NULL);
  820.         return TCL_ERROR;
  821.     }                     
  822.     objectPtr =  TSippObjectHandleToPtr (tSippGlobPtr, argv [1]);
  823.     if (objectPtr == NULL)
  824.         return TCL_ERROR;
  825.     if (!TSippConvertVertex (tSippGlobPtr, argv [2], &translation))
  826.         return TCL_ERROR;
  827.  
  828.     object_move (objectPtr, translation.x, translation.y, translation.z);
  829.  
  830.     return TCL_OK;
  831.  
  832. } /* SippObjectMove */
  833.  
  834. /*=============================================================================
  835.  * TSippObjectInit --
  836.  *   Initialized the object commands, including creating the object table.
  837.  *
  838.  * Parameters:
  839.  *   o tSippGlobP (I) - Pointer to the top level global data structure.
  840.  *-----------------------------------------------------------------------------
  841.  */
  842. void
  843. TSippObjectInit (tSippGlobPtr)
  844.     tSippGlob_pt    tSippGlobPtr;
  845. {
  846.     static tSippTclCmdTbl_t cmdTable [] = {
  847.         {"SippObjectCreate",      SippObjectCreate},
  848.         {"SippObjectDelete",      SippObjectDelete},
  849.         {"SippObjectInstance",    SippObjectInstance},
  850.         {"SippObjectDup",         SippObjectDup},
  851.         {"SippObjectDeepDup",     SippObjectDeepDup},
  852.         {"SippObjectGetTransf",   SippObjectGetTransf},
  853.         {"SippObjectSetTransf",   SippObjectSetTransf},
  854.         {"SippObjectClearTransf", SippObjectClearTransf},
  855.         {"SippObjectTransform",   SippObjectTransform},
  856.         {"SippObjectDelete",      SippObjectDelete},
  857.         {"SippObjectAddSurface",  SippObjectAddSurface},
  858.         {"SippObjectSubSurface",  SippObjectSubSurface},
  859.         {"SippObjectAddSubobj",   SippObjectAddSubobj},
  860.         {"SippObjectSubSubobj",   SippObjectSubSubobj},
  861.         {"SippObjectRotateX",     SippObjectRotateX},
  862.         {"SippObjectRotateY",     SippObjectRotateY},
  863.         {"SippObjectRotateZ",     SippObjectRotateZ},
  864.         {"SippObjectRotate",      SippObjectRotate},
  865.         {"SippObjectScale",       SippObjectScale},
  866.         {"SippObjectMove",        SippObjectMove},
  867.         {NULL,                    NULL}
  868.     };
  869.  
  870.     tSippGlobPtr->objectTblPtr = 
  871.         Tcl_HandleTblInit ("object", sizeof (Object *), 24);
  872.  
  873.     TSippInitCmds (tSippGlobPtr, cmdTable);
  874.  
  875. } /* TSippObjectInit */
  876.